<template>
  <div class="process-panel__container" :style="{ width: `${this.width}px` }">
    <el-tabs v-model="activeName" type="card" style="margin-top: 5px">
      <el-tab-pane label="原始设置" name="first">
        <el-collapse v-model="activeTab">
          <el-collapse-item name="base">
            <div slot="title" class="panel-tab__title">
              <i class="el-icon-info"></i>常规
            </div>
            <element-base-info
              :id-edit-disabled="idEditDisabled"
              :business-object="elementBusinessObject"
              :type="elementType"
              :model="model"
            />
          </el-collapse-item>
          <el-collapse-item
            name="condition"
            v-if="elementType === 'Process'"
            key="message"
          >
            <div slot="title" class="panel-tab__title">
              <i class="el-icon-s-comment"></i>消息与信号
            </div>
            <signal-and-massage />
          </el-collapse-item>
          <el-collapse-item
            name="condition"
            v-if="conditionFormVisible"
            key="condition"
          >
            <div slot="title" class="panel-tab__title">
              <i class="el-icon-s-promotion"></i>流转条件
            </div>
            <flow-condition
              :business-object="elementBusinessObject"
              :type="elementType"
            />
          </el-collapse-item>
          <el-collapse-item name="condition" v-if="formVisible" key="form">
            <div slot="title" class="panel-tab__title">
              <i class="el-icon-s-order"></i>表单
            </div>
            <element-form :id="elementId" :type="elementType" />
            <!-- 友情提示：使用 <router-link target="_blank" :to="{path:'/bpm/manager/form'}"><el-link type="danger">流程表单</el-link> </router-link>
        替代，提供更好的表单设计功能 -->
          </el-collapse-item>
          <el-collapse-item
            name="task"
            v-if="elementType.indexOf('Task') !== -1"
            key="task"
          >
            <div slot="title" class="panel-tab__title">
              <i class="el-icon-s-claim"></i>任务
            </div>
            <element-task :id="elementId" :type="elementType" />
          </el-collapse-item>
          <el-collapse-item
            name="multiInstance"
            v-if="elementType.indexOf('Task') !== -1"
            key="multiInstance"
          >
            <div slot="title" class="panel-tab__title">
              <i class="el-icon-s-help"></i>多实例
            </div>
            <element-multi-instance
              ref="child2Container"
              :business-object="elementBusinessObject"
              :type="elementType"
            />
          </el-collapse-item>
          <el-collapse-item name="listeners" key="listeners">
            <div slot="title" class="panel-tab__title">
              <i class="el-icon-message-solid"></i>执行监听器
            </div>
            <element-listeners :id="elementId" :type="elementType" />
          </el-collapse-item>
          <el-collapse-item
            name="taskListeners"
            v-if="elementType === 'UserTask'"
            key="taskListeners"
          >
            <div slot="title" class="panel-tab__title">
              <i class="el-icon-message-solid"></i>任务监听器
            </div>
            <user-task-listeners :id="elementId" :type="elementType" />
          </el-collapse-item>
          <el-collapse-item name="extensions" key="extensions">
            <div slot="title" class="panel-tab__title">
              <i class="el-icon-circle-plus"></i>扩展属性
            </div>
            <element-properties :id="elementId" :type="elementType" />
          </el-collapse-item>
          <el-collapse-item name="other" key="other">
            <div slot="title" class="panel-tab__title">
              <i class="el-icon-s-promotion"></i>其他
            </div>
            <element-other-config :id="elementId" />
          </el-collapse-item>
          <el-collapse-item
            name="subprocess"
            key="subprocess"
            v-if="callActivityVisible"
          >
            <div slot="title" class="panel-tab__title">
              <i class="el-icon-info"></i>绑定子流程
            </div>
            <element-subprocess-config
              :id="elementId"
              :optionData="subProcessData"
            />
          </el-collapse-item> </el-collapse
      ></el-tab-pane>
      <el-tab-pane label="审批人" v-if="approverVisible" name="second">
        <approver-config
          :id="elementId"
          @updateMultinstance="updateMultinstanceOperate"
        />
      </el-tab-pane>
      <el-tab-pane label="审批按钮" v-if="approverVisible" name="third">
        <approval-button-config :id="elementId" />
      </el-tab-pane>
      <!-- <el-tab-pane label="设置字段权限" v-if="approverVisible">
        <form-authority-config name="fourth"/>
      </el-tab-pane> -->
      <el-tab-pane label="时间设置" v-if="approverVisible" name="fifth">
        <time-config :id="elementId" />
      </el-tab-pane>
      <el-tab-pane
        label="条件节点设置"
        v-if="conditionFormVisible"
        name="sixth"
      >
        <condition-node-Config
          :id="elementId"
          :conditionNodeData="conditionNodeData"
        />
      </el-tab-pane>
    </el-tabs>
  </div>
</template>
<script>
import ElementSubprocessConfig from "./subprocess/ElementSubprocessConfig.vue";
import ElementBaseInfo from "./base/ElementBaseInfo";
import ElementOtherConfig from "./other/ElementOtherConfig";
import ElementTask from "./task/ElementTask";
import ElementMultiInstance from "./multi-instance/ElementMultiInstance";
import FlowCondition from "./flow-condition/FlowCondition";
import SignalAndMassage from "./signal-message/SignalAndMessage";
import ElementListeners from "./listeners/ElementListeners";
import ElementProperties from "./properties/ElementProperties";
import ElementForm from "./form/ElementForm";
import UserTaskListeners from "./listeners/UserTaskListeners";
import FormAuthorityConfig from "./config/FormAuthorityConfig.vue";
import ApproverConfig from "./config/ApproverConfig.vue";
import ApprovalButtonConfig from "./config/ApprovalButtonConfig.vue";
import TimeConfig from "./config/timeConfig.vue";
import ConditionNodeConfig from "./config/ConditionNodeConfig.vue";
import { getDeployments } from "@/api/bpm/task";
import { getAllOpenForms } from "@/api/bpm/form.js";

/**
 * 侧边栏
 * @Author MiyueFE
 * @Home https://github.com/miyuesc
 * @Date 2021年3月31日18:57:51
 */
export default {
  name: "MyPropertiesPanel",
  components: {
    UserTaskListeners,
    ElementForm,
    ElementProperties,
    ElementListeners,
    SignalAndMassage,
    FlowCondition,
    ElementMultiInstance,
    ElementTask,
    ElementOtherConfig,
    ElementBaseInfo,
    FormAuthorityConfig,
    ApproverConfig,
    ApprovalButtonConfig,
    TimeConfig,
    ElementSubprocessConfig,
    ConditionNodeConfig,
  },
  componentName: "MyPropertiesPanel",
  props: {
    bpmnModeler: Object,
    prefix: {
      type: String,
      default: "camunda",
    },
    width: {
      type: Number,
      default: 543,
    },
    idEditDisabled: {
      type: Boolean,
      default: false,
    },
    model: Object, // 流程模型的数据
  },
  provide() {
    return {
      prefix: this.prefix,
      width: this.width,
    };
  },
  data() {
    return {
      subProcessData: [],
      conditionNodeData: [],
      activeName: "first",
      activeTab: "base",
      elementId: "",
      elementType: "",
      elementBusinessObject: {}, // 元素 businessObject 镜像，提供给需要做判断的组件使用
      conditionFormVisible: false, // 流转条件设置
      formVisible: false, // 表单配置
      approverVisible: false, //审批人tab是否显示
      callActivityVisible: false, //绑定子流程是否显示
      // formList: [],
      // selectFormId: '' // 选择的是哪个表单id
    };
  },
  watch: {
    elementId: {
      handler() {
        this.activeTab = "base";
      },
    },
  },
  created() {
    const modelId = this.$route.query && this.$route.query.modelId;
    this.initModels();
    //获取所有已发布的流程，用来供子流程选择
    getDeployments().then((res) => {
      this.subProcessData = res.data;
    });
    //获取动态表单数据，用于条件流转时获取发布的表单数据
    getAllOpenForms().then((response) => {
      this.conditionNodeData = response.data;
    });
  },
  methods: {
    updateMultinstanceOperate({ type, num }) {
      //选择是会签还是或签的方法
      let contsiner = this.$refs.child2Container;
      if (type === "Null") {
        contsiner.changeLoopCharacteristicsType("Null");
        return;
      }
      contsiner.changeLoopCharacteristicsType("ParallelMultiInstance");
      //循环基数
      contsiner.updateLoopCardinality(String(num));
      //元素变量
      contsiner.loopInstanceForm.elementVariable = "${assigneeList}";
      contsiner.updateLoopBase();
      //完成条件
      let condition =
        type === "ParallelMultiInstance"
          ? "${nrOfCompletedInstances==nrOfInstances}"
          : "${nrOfCompletedInstances>=1}";
      contsiner.updateLoopCondition(condition);
    },
    initModels() {
      // 初始化 modeler 以及其他 moddle
      if (!this.bpmnModeler) {
        // 避免加载时 流程图 并未加载完成
        this.timer = setTimeout(() => this.initModels(), 10);
        return;
      }
      if (this.timer) clearTimeout(this.timer);
      window.bpmnInstances = {
        modeler: this.bpmnModeler,
        modeling: this.bpmnModeler.get("modeling"),
        moddle: this.bpmnModeler.get("moddle"),
        eventBus: this.bpmnModeler.get("eventBus"),
        bpmnFactory: this.bpmnModeler.get("bpmnFactory"),
        elementFactory: this.bpmnModeler.get("elementFactory"),
        elementRegistry: this.bpmnModeler.get("elementRegistry"),
        replace: this.bpmnModeler.get("replace"),
        selection: this.bpmnModeler.get("selection"),
      };
      this.getActiveElement();
    },
    getActiveElement() {
      // 初始第一个选中元素 bpmn:Process
      this.initFormOnChanged(null);
      this.bpmnModeler.on("import.done", (e) => {
        this.initFormOnChanged(null);
      });
      // 监听选择事件，修改当前激活的元素以及表单
      this.bpmnModeler.on("selection.changed", ({ newSelection }) => {
        this.initFormOnChanged(newSelection[0] || null);
      });
      this.bpmnModeler.on("element.changed", ({ element }) => {
        // 保证 修改 "默认流转路径" 类似需要修改多个元素的事件发生的时候，更新表单的元素与原选中元素不一致。
        if (element && element.id === this.elementId) {
          this.initFormOnChanged(element);
        }
      });
    },
    // 初始化数据
    initFormOnChanged(element) {
      let activatedElement = element;
      if (!activatedElement) {
        activatedElement =
          window.bpmnInstances.elementRegistry.find(
            (el) => el.type === "bpmn:Process"
          ) ??
          window.bpmnInstances.elementRegistry.find(
            (el) => el.type === "bpmn:Collaboration"
          );
      }
      if (!activatedElement) return;
      //debugger;
      console.log(`
              ----------
      select element changed:
                id:  ${activatedElement.id}
              type:  ${activatedElement.businessObject.$type}
              ----------
              `);
      console.log("businessObject: ", activatedElement.businessObject);
      window.bpmnInstances.bpmnElement = activatedElement;
      this.bpmnElement = activatedElement;
      this.elementId = activatedElement.id;
      this.elementType = activatedElement.type.split(":")[1] || "";
      this.elementBusinessObject = JSON.parse(
        JSON.stringify(activatedElement.businessObject)
      );
      this.callActivityVisible = this.elementType === "CallActivity";
      this.formVisible =
        this.elementType === "UserTask" || this.elementType === "StartEvent";
      this.conditionFormVisible = false;
      this.approverVisible = false;
      if (this.elementType === "UserTask") {
        this.approverVisible = true;
        this.activeName =
          this.activeName != "first" && this.activeName != "sixth"
            ? this.activeName
            : "first";
      } else if (
        //设置网关类型下才能进行各个条件的流转
        this.elementType === "SequenceFlow" &&
        activatedElement.source &&
        activatedElement.source.type.indexOf("Gateway") > 0
        //activatedElement.source.type.indexOf("StartEvent") === -1
      ) {
        this.conditionFormVisible = true;
        this.activeName =
          this.activeName == "sixth" ? this.activeName : "first";
      } else {
        this.activeName = "first";
      }
    },
    beforeDestroy() {
      window.bpmnInstances = null;
    },
  },
};
</script>
